////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// Copyright (c) 2016-2018 Qualcomm Technologies, Inc.
// All Rights Reserved.
// Confidential and Proprietary - Qualcomm Technologies, Inc.
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// @file  camxcaecstatsprocessor.h
/// @brief The class that implements IStatsProcessor for AEC.
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

#ifndef CAMXCAECSTATSPROCESSOR_H
#define CAMXCAECSTATSPROCESSOR_H

#include "chiaecinterface.h"
#include "chistatsproperty.h"
#include "camxtuningdatamanager.h"
#include "camxaecengine.h"
#include "camxistatsprocessor.h"
#include "camxlist.h"
#include "camxstatsparser.h"
#include "camxutils.h"
#include "parametertuningtypes.h"

CAMX_NAMESPACE_BEGIN

static const INT AECSettleUnknown                  = -1;     ///< Invalid/Unknown AEC settle state - Initial
static const INT AECSettleFalse                    = 0;      ///< AEC settle flag is false from algo
static const INT AECSettled                        = 1;      ///< AEC settle flag is true  from algo
static const INT AECompensation0                   = 0;      ///< AEC Compensation for Invalid
static const INT AECompensation_Beach_Snow         = 6;      ///< AEC Compensation for Beach Snow scene
static const INT AECompensation_Sunset_CandleLight = -6;     ///< AEC Compensation for Sunset and Candle light
static const INT AESensitivity_Sports              = 400;    ///< AEC Compensation for Sports
static const UINT32 AECAlgoGetMaxInputParamCount   =  2;     ///< Maximum Number of input params for Get
static const UINT16 AECExposureProgramManual       = 1;      ///< Manual Exposure Program
static const UINT16 AECExposureProgramNormal       = 2;      ///< Normal Exposure Program
/// @brief This structure holds AWB property dependency List
struct AECPropertyDependency
{
    UINT64      slotNum;    ///< The request id for the statistics
    PropertyID  propertyID; ///< Property dependencies in this unit
};

/// @brief This structure holds AEC property dependency List
struct AECPropertyDependencyList
{
    INT32                   propertyCount;                  ///< Number of properties in this unit
    AECPropertyDependency   properties[MaxStatsProperties]; ///< Property dependencies in this unit
};

/// @brief This structure holds AEC related vendor tag
struct AECVendorTagList
{
    UINT32        metaTag;           ///< metaTag
    CamxResult    result;            ///< result
    const CHAR*   pTagName;          ///< pTagName
    const CHAR*   pSectionName;      ///< pSectionName
    VOID*         pData;             ///< data
    UINT32        size;              ///< size
};
/// Forward Declarations
class Node;

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// @brief The class that implements IStatsProcessor for AEC.
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
class CAECStatsProcessor final : public IStatsProcessor
{
public:
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// Create
    ///
    /// @brief  Create the object for CAECStatsProcessor.
    ///
    /// @param  ppAECStatsProcessor Pointer to CAECStatsProcessor
    ///
    /// @return CamxResultSuccess if successful
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    static CamxResult Create(
        IStatsProcessor** ppAECStatsProcessor);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// Initialize
    ///
    /// @brief  Used to initialize the class.
    ///
    /// @param  pInitializeData Pointer to initial settings
    ///
    /// @return CamxResultSuccess if successful
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    virtual CamxResult Initialize(
        const StatsInitializeData* pInitializeData);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// ExecuteProcessRequest
    ///
    /// @brief  Executes the algorithm for a request.
    ///
    /// @param  pStatsProcessRequestDataInfo Pointer to process request information
    ///
    /// @return CamxResultSuccess if successful
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    virtual CamxResult ExecuteProcessRequest(
        const StatsProcessRequestData* pStatsProcessRequestDataInfo);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// VendorTagListAllocation
    ///
    /// @brief  Function to fetch vendor tag list and allocate memory for them
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult VendorTagListAllocation();

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// AddOEMDependencies
    ///
    /// @brief  Get the list of OEM dependencies from all stats processors.
    ///
    /// @param  pStatsProcessRequestDataInfo    Pointer to process request information
    /// @param  pStatsDependency                Pointer to list of property dependencies
    ///
    /// @return CamxResultSuccess if successful
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult AddOEMDependencies(
        const StatsProcessRequestData*  pStatsProcessRequestDataInfo,
        StatsDependency*                pStatsDependency);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// GetDependencies
    ///
    /// @brief  Get the the list of dependencies from all stats processors.
    ///
    /// @param  pStatsProcessRequestDataInfo    Pointer to process request information
    /// @param  pStatsDependency                Pointer to stats dependencies
    ///
    /// @return CamxResultSuccess if successful
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    virtual CamxResult GetDependencies(
        const StatsProcessRequestData* pStatsProcessRequestDataInfo,
        StatsDependency*               pStatsDependency);

private:
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// CAECStatsProcessor
    ///
    /// @brief  constructor
    ///
    /// @return None
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CAECStatsProcessor();

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// ~CAECStatsProcessor
    ///
    /// @brief  destructor
    ///
    /// @return None
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    ~CAECStatsProcessor();

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// OverwriteAECOutput
    ///
    /// @brief  Overwrite the value from algorithm output
    ///
    /// @param  pOutput Pointer to AEC Engine's output
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult OverwriteAECOutput(
        AECEngineProcessStatsOutput* pOutput
        ) const;

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// GetVendorTags
    ///
    /// @brief  Gets the required inputs for the core algorithm
    ///
    /// @param  pStatsProcessRequestDataInfo Pointer to process request information
    /// @param  pInput                       Pointer to the core input data
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult GetVendorTags(
        const StatsProcessRequestData* pStatsProcessRequestDataInfo,
        AECEngineAlgorithmInput*       pInput);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// GetChiStatsSession
    ///
    /// @brief  Get the stats chi session data.
    ///
    /// @param  pStatsProcessRequestDataInfo    Pointer to process request information
    /// @param  pInput                          Pointer to the core input data
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult GetChiStatsSession(
        const StatsProcessRequestData* pStatsProcessRequestDataInfo,
        AECEngineAlgorithmInput*       pInput);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// GetAlgoInput
    ///
    /// @brief  Gets the required inputs for the core algorithm
    ///
    /// @param  pStatsProcessRequestDataInfo Pointer to process request information
    /// @param  pInput                       Pointer to the core input data
    /// @param  pHALParam                    Pointer AECEngineHALParam to save the HAL parameters
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult GetAlgoInput(
        const StatsProcessRequestData* pStatsProcessRequestDataInfo,
        AECEngineAlgorithmInput*       pInput ,
        AECEngineHALParam*              pHALParam);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// SetDebugDataPointer
    ///
    /// @brief  Sets the debug data pointer to the algorithm
    ///
    /// @param  pStatsProcessRequestDataInfo Pointer to process request information
    /// @param  pInput                       Pointer to the core input data
    ///
    /// @return None
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    virtual VOID SetDebugDataPointer(
        const StatsProcessRequestData* pStatsProcessRequestDataInfo,
        AECEngineAlgorithmInput*       pInput);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// SetCameraInformation
    ///
    /// @brief  Sets the camera information to the algorithm
    ///
    /// @param  pStatsProcessRequestDataInfo Pointer to process request information
    /// @param  pInput                       Pointer to the core input data
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult SetCameraInformation(
        const StatsProcessRequestData* pStatsProcessRequestDataInfo,
        AECEngineAlgorithmInput*       pInput);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PrepareAlgorithmOutput
    ///
    /// @brief  Prepare the data used by algorithm to output it's result for processing the stats
    ///
    /// @param  pOutput   Pointer to AECEngineProcessStatsOutput
    /// @param  requestId ID of the request being serviced
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PrepareAlgorithmOutput(
        AECEngineProcessStatsOutput* pOutput,
        UINT64                       requestId
        ) const;

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// SetAlgoChromatix
    ///
    /// @brief  Sets the required inputs parameters for the core algorithm
    ///
    /// @param  pInputTuningModeData Pointer to Tuning mode data
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult SetAlgoChromatix(
        ChiTuningModeParameter* pInputTuningModeData);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// SetAlgoSetParams
    ///
    /// @brief  Sets the required inputs parameters for the core algorithm
    ///
    /// @param  pHALParam The pointer AECEngineHALParam to save the HAL parameters
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult SetAlgoSetParams(
        AECEngineHALParam* pHALParam);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PublishVendorTagMetadata
    ///
    /// @brief  Publishes AEC Vendor tag output to the metadata pool
    ///
    /// @param  pVendorTagOutput                List of vendor tag outputs to be published
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PublishVendorTagMetadata(
        StatsVendorTagList*             pVendorTagOutput);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// AllocateMemoryVendorTag
    ///
    /// @brief  It goes through all vendor tag list and allocate memory to hold the vendor tag data
    ///
    /// @param  pVendorTagInfoList pointer to vendor tag list
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult AllocateMemoryVendorTag(
        StatsVendorTagInfoList* pVendorTagInfoList);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PublishMetadata
    ///
    /// @brief  Publishes all necessary camera metadata to all needed pools
    ///
    /// @param  pOutput                      Pointer to core algorithm's output
    /// @param  pHALParam                    Pointer AECEngineHALParam to save the HAL parameters
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PublishMetadata(
        AECEngineProcessStatsOutput* pOutput,
        AECEngineHALParam*           pHALParam);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PublishPropertyPoolFrameControl
    ///
    /// @brief  Publishes the algorithm output to control future frames to the main metadata pool
    ///
    /// @param  pOutput                      Pointer to core algorithm's output
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PublishPropertyPoolFrameControl(
        AECEngineProcessStatsOutput*   pOutput);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PublishPropertyPoolAdditionalFrameControl
    ///
    /// @brief  Publishes the algorithm additional output to control future frames to the main metadata pool
    ///
    /// @param  pOutput                      Pointer to core algorithm's output
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PublishPropertyPoolAdditionalFrameControl(
        AECEngineProcessStatsOutput*   pOutput);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PublishPropertyPoolFrameInfo
    ///
    /// @brief  Publishes the algorithm output describing the frame to the main metadata pool
    ///
    /// @param  pOutput                      Pointer to core algorithm's output
    /// @param  pHALParam                    Pointer AECEngineHALParam to save the HAL parameters
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PublishPropertyPoolFrameInfo(
        AECEngineProcessStatsOutput*   pOutput,
        AECEngineHALParam*             pHALParam);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PublishExternalCameraMetadata
    ///
    /// @brief  Publishes the mandated camera metadata
    ///
    /// @param  pOutput                      Pointer to core algorithm's output
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PublishExternalCameraMetadata(
        AECEngineProcessStatsOutput*   pOutput);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PublishPropertyPoolInternal
    ///
    /// @brief  Publishes the algorithm output to the internal metadata pool
    ///
    /// @param  pOutput                      Pointer to core algorithm's output
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PublishPropertyPoolInternal(
        AECEngineProcessStatsOutput*   pOutput);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PublishPropertyDebugData
    ///
    /// @brief  Publishes the debug-data
    ///
    /// @return CamxResultSuccess if successful
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PublishPropertyDebugData();

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PublishPreRequestOutput
    ///
    /// @brief  Publishes the output for first two slots. This will be done even before the first
    ///         process request comes. The output from stats node will be used by the dependent nodes.
    ///
    /// @param  pUsecasePool Pointer to the usecase pool
    ///
    /// @return CamxResultSuccess if successful
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PublishPreRequestOutput(
        MetadataPool* pUsecasePool);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PublishDefaultOutput
    ///
    /// @brief  Publishes the output for first frames
    ///
    /// @return CamxResultSuccess if successful
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PublishDefaultOutput();

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PublishCrossProperty
    ///
    /// @brief  Publish AEC cross pipeline property for dual camera usecase.
    ///
    /// @param  pStatsProcessRequestDataInfo Pointer to process request information
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PublishCrossProperty(
        const StatsProcessRequestData* pStatsProcessRequestDataInfo);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// SetAlgoBayerGridValue
    ///
    /// @brief  Set the Bayer Grid statistic data to pBayerGrid for the algorithm to consume
    ///
    /// @param  pISPHDRStats Pointer to the internal property blob to read from
    /// @param  pHDRBEOutput Pointer to the internal property blob to read from
    /// @param  pBayerGrid   The Bayer Grid statistic data to set the values to
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult SetAlgoBayerGridValue(
    PropertyISPHDRBEStats*  pISPHDRStats,
    ParsedHDRBEStatsOutput* pHDRBEOutput,
    StatsBayerGrid*         pBayerGrid);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// SetAlgoBayerHDRBHistValue
    ///
    /// @brief  Set the Bayer Histogram statistic data for the algorithm to consume
    ///
    /// @param  pHDRBHistStatsOutput    Pointer to the ParsedHDRBhistStatsOutput to read from
    /// @param  pBayerHistogram         Pointer to the Bayer Histogram statistic data to write to as algorithm input
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult SetAlgoBayerHDRBHistValue(
        ParsedHDRBHistStatsOutput*  pHDRBHistStatsOutput,
        StatsBayerHist*             pBayerHistogram);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// SetAlgoBayerHistValue
    ///
    /// @brief  Set the Bayer Histogram statistic data to pBHistStatsOutput
    ///
    /// @param  pBHistStatsOutput    Pointer to the ParsedBHistStatsOutput from ISP
    /// @param  pBayerHistogram      Pointer to the Bayer Histogram statistic data to be used as algorithm input
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult SetAlgoBayerHistValue(
        ParsedBHistStatsOutput*  pBHistStatsOutput,
        StatsBayerHist*          pBayerHistogram);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PopulatePropPoolFrameControl
    ///
    /// @brief  Populates the algorithm output for the frame control on main metadata pool
    ///
    /// @param  pOutput                 Pointer to core algorithm's output
    /// @param  pFrameControl           Pointer to AEC frame control within the main metadata pool
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PopulatePropPoolFrameControl(
        AECEngineProcessStatsOutput* pOutput,
        AECFrameControl*             pFrameControl);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PopulatePropPoolPeerControl
    ///
    /// @brief  Populates the algorithm output for the Peer Info control on main metadata pool
    ///
    /// @param  pOutput         Pointer to core algorithm's output
    /// @param  ppPeerInfo      Pointer to Pointer of Peer Info.
    ///
    /// @return None
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    VOID PopulatePropPoolPeerControl(
        AECEngineProcessStatsOutput* pOutput,
        VOID**                       ppPeerInfo);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PopulatePropPoolStatsControl
    ///
    /// @brief  Populates the algorithm output for the Stats control on main metadata pool
    ///
    /// @param  pOutput         Pointer to core algorithm's output
    /// @param  pFrameControl   Pointer to AEC Stats control within the main metadata pool
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PopulatePropPoolStatsControl(
        AECEngineProcessStatsOutput* pOutput,
        AECStatsControl*             pFrameControl);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PopulatePropPoolFrameInfo
    ///
    /// @brief  Populates the algorithm output for the frame information on main metadata pool
    ///
    /// @param  pOutput     Pointer to core algorithm's output
    /// @param  pFrameInfo  Pointer to AEC frame information within the main metadata pool
    /// @param  pHALParam   Pointer AECEngineHALParam to save the HAL parameters
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PopulatePropPoolFrameInfo(
        AECEngineProcessStatsOutput* pOutput,
        AECFrameInformation*         pFrameInfo,
        AECEngineHALParam*           pHALParam);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PopulatePropPoolInternal
    ///
    /// @brief  Populates the algorithm output to the internal metadata pool
    ///
    /// @param  pOutput         Pointer to core algorithm's output
    /// @param  pInternalOutput Pointer to AEC internal output
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult PopulatePropPoolInternal(
        AECEngineProcessStatsOutput* pOutput,
        AECOutputInternal*           pInternalOutput);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// ReadHALAECParam
    ///
    /// @brief  Read the HAL's input for AEC
    ///
    /// @param  pHALParam                    Pointer for AECEngineHALParam to save the HAL parameters
    /// @param  pStatsProcessRequestDataInfo Pointer to Stats Process Request Data Info
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult ReadHALAECParam(
       AECEngineHALParam*             pHALParam,
       const StatsProcessRequestData* pStatsProcessRequestDataInfo
       ) const;

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// GetHardwareInfo
    ///
    /// @brief  Fills in the hardware information
    ///
    /// @param  pHardwareInfo       The hardware capabilities information to be filled in
    /// @param  pHardwareContext    The hardware context
    /// @param  cameraID            The camera ID for the sensor in interest
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult GetHardwareInfo(
        AECEngineHWInfo*    pHardwareInfo,
        HwContext*          pHardwareContext,
        INT32               cameraID
        ) const;

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// GetPeerInfo
    ///
    /// @brief  Fills in the Peer information
    ///
    /// @param  pStatsProcessRequestDataInfo  Pointer to Stats Process Request Data Info
    /// @param  ppPeerInfo                    Pointer of Pointer of Peer Information
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult GetPeerInfo(
        const StatsProcessRequestData* pStatsProcessRequestDataInfo,
        VOID**                         ppPeerInfo
    ) const;

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// GetCropWindow
    ///
    /// @brief  Fills in the stats crop window
    ///
    /// @param  pCropWindow     The stats crop window
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult GetCropWindow(
        StatsRectangle* pCropWindow
        ) const;

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// UpdateTraceEvents
    ///
    /// @brief  Updates the trace events based on the processed stats output
    ///
    /// @param  pProcessStatsOutput  The output of processed stats
    ///
    /// @return None
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    VOID UpdateTraceEvents(
        AECEngineProcessStatsOutput* pProcessStatsOutput);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// SetStatsConfigFromAlgoConfig
    ///
    /// @brief  This method sets the complete stats configuration based on algorithm's stats configuration
    ///
    /// @param  pAlgoStatsConfig       Statistics configuration received from the algorithm
    /// @param  pAlgoBHISTStatsConfig  BHIST Statistics configuration received from the algorithm
    /// @param  pStatsConfig           Output statistics configuration to be set for
    ///
    /// @return None
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    VOID SetStatsConfigFromAlgoConfig(
        StatsBayerGridBayerExposureConfig*  pAlgoStatsConfig,
        StatsBayerHistogramConfig*          pAlgoBHISTStatsConfig,
        AECConfig*                          pStatsConfig) const;

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// SetTouchROISettings
    ///
    /// @brief  Read the HAL's input for best shot mode and configure settigns to AEC
    ///
    /// @param  pHALParam     The pointer AECEngineHALParam to save the HAL parameters
    /// @param  pTouchROIInfo The pointer WeightedRectangle to save the HAL parameters
    ///
    /// @return None
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    VOID SetTouchROISettings(
        AECEngineHALParam*      pHALParam,
        WeightedRectangle*      pTouchROIInfo
    ) const;

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// SetFaceROISettings
    ///
    /// @brief  Read the HAL's input for best shot mode and configure settigns to AEC
    ///
    /// @param  pHALParam    The pointer AECEngineHALParam to save the HAL parameters
    /// @param  pFaceROIInfo The pointer PropertyFaceROIInfo to save the HAL parameters
    ///
    /// @return None
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    VOID SetFaceROISettings(
        AECEngineHALParam*     pHALParam,
        FaceROIInformation*    pFaceROIInfo
    ) const;

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// SetBestShotModeSettings
    ///
    /// @brief  Read the HAL's input for best shot mode and configure settigns to AEC
    ///
    /// @param  pHALParam The pointer AECEngineHALParam to save the HAL parameters
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult SetBestShotModeSettings(
        AECEngineHALParam* pHALParam
    ) const;

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// GetFlashInfoType
    ///
    /// @brief  Convert the Algo flash type (PRE/MAIN) to AEC Property pool type
    ///
    /// @param  flashState Flash type passed from Algo
    ///
    /// @return flashType converted to property pool type
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    AECFlashInfoType GetFlashInfoType(
        AECAlgoFlashStateType flashState
    ) const;

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// SetISOExpPriorityValue
    ///
    /// @brief  Set ISO or Exposure Time priority based on priority param from HAL
    ///
    /// @param  pHALParam Pointer to AECEngineHALParam where the function retrieves the ISO/Exposure Time priority
    ///
    /// @return None
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    VOID SetISOExpPriorityValue(
        AECEngineHALParam* pHALParam
    ) const;

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// ReadAFDMode
    ///
    /// @brief  Read the HAL's Anti Banding Mode input and AFD output and configure AFD mode to AEC
    ///
    /// @param  pHALParam The pointer AECEngineHALParam to save the HAL parameters
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult ReadAFDMode(
        AECEngineHALParam* pHALParam
    ) const;

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// ReadStatsNodesUpdates
    ///
    /// @brief  Gets the updates from other Nodes: AF, AWB, AFD, ASD for previous frame
    ///
    /// @param  pAECNodesUpdate  Pointer to AEC input structure
    ///
    /// @return Success or failure
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CamxResult ReadStatsNodesUpdates(
        AECEngineNodesUpdate* pAECNodesUpdate
    ) const;

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CAECStatsProcessor(const CAECStatsProcessor&)               = delete;   ///< Do not implement copy constructor
    CAECStatsProcessor& operator=(const CAECStatsProcessor&)    = delete;   ///< Do not implement assignment operator

    Node*                        m_pNode;               ///< Pointer to owning StatsProcessor node
    MetadataPool*                m_pDebugDataPool;      ///< Pointer to debugdata metadata pool
    StatsParser*                 m_pStatsParser;        ///< ISP stats parser
    CAECEngine*                  m_pAECEngine;          ///< Pointer to CAECEngine instance
    AECEngineHWInfo              m_hardwareInfo;        ///< AEC engine hardware info

    INT                          m_lastSettledState;    ///< Indicate if AEC is settled in last request
    AECEngineAlgorithmInput      m_algoInput;           ///< Input for algorithm when processing the data
    AECEngineProcessStatsOutput  m_engineStatsOutput;   ///< Output used by AEC Engine to save the output from algorithm
    CREATEAEC                    m_pfnCreate;           ///< Function Pointer to create Algorithm instance

    StatsVendorTagInfoList       m_vendorTagInputList;                               ///< List of Stats vendor tag dependency
    StatsVendorTagInfoList       m_vendorTagInfoOutputputList;                       ///< List of Algo's output vendor tags
    StatsVendorTagList           m_algoVendorTagOutputList;                          ///< Pointer to Algo VendorTagOutputlist
    StatsTuningData              m_tuningData;                                       ///< Tuning data set
    UINT64                       m_currProcessingRequestId;                          ///< Current processing request Id
    BOOL                         m_skipProcessing;                                   ///< algo processing skip flag
    UINT                         m_peerpipelineId;                                   ///< Peer Pipeline Id
    UINT                         m_cameraId;                                         ///< Camera Id
    AECCommandOutputParam        m_outputParam;                                      ///< Algo output param
    AECEngineHALParam            m_HALParam;                                         ///< input HAL Param
};

CAMX_NAMESPACE_END

#endif // CAMXCAECSTATSPROCESSOR_H
